<template>
    <div :class="classes" v-show="navList.length > 0">
      <div class="tabs-wrap">
        <ul :class="[this.type ? 'card' : 'default','tabs-header',]" ref="tabsHeader" :style="{width: hiddenList.length > 0 ? `calc(100% - ${moreWidth} + ${(navList.length - 1) * 4}px)` : ''}">
          <li
            v-for="(n, i) in navList" :key="i"
            :style="{width: hiddenList.length > 0 ? `${100 / navList.length}%` : '', zIndex: navList.length - i, padding: minPadding, minWidth: !showInner ? (sizes !== 'large' ? '31.5px' : '37.8px') : ''}"
            :class="['sh-tabs-title', {'sh-tabs-disabled': n.disabled,'sh-tabs-active': n.active, 'not-first': i > 0}]"
            @click="clickHeader(n)" >
              <Icon v-if="n.icon" :type="n.icon" />
              <span ref="span">{{showInner ? n.label : ''}}</span>
              <Icon v-if="n.closed && !n.disabled"
              type="icon-close-bg"
              class="close-icon"
              @click.stop="closeTab(n.name)" />
          </li>
        </ul>
      </div>
      <div class="more-btn" v-if="hiddenList.length > 0" @click.stop="showHidden = !showHidden" v-outside.capture="() => showHidden = false">
        <Icon type="icon-more" />
        <ul class="hidden-ul" v-show="showHidden">
          <li
            v-for="(h, v) in hiddenList" :key="v"
            :class="['sh-tabs-title', {'sh-tabs-disabled': h.disabled,'sh-tabs-active': h.active}]"
            @click="clickHeader(h)" >
            <Icon v-if="h.icon" :type="h.icon" />
            <span ref="span">{{h.label}}</span>
            <Icon v-if="h.closed && !h.disabled"
              type="icon-close-bg"
              class="close-icon"
              @click.stop="closeTab(h.name)" />
          </li>
          <!-- 下个需求做 -->
          <!-- <li class="close-all" @click.stop="closeAll">关闭所有页面</li> -->
        </ul>
      </div>
      <div class="sh-tabs-content">
        <slot></slot>
      </div>
    </div>
</template>

<script>
import Icon from '../../icon'
import outside from '../../../directives/clickoutside'
import size from '../../../mixins/size'
export default {
  name: 'Tabs',
  mixins: [size],
  components: {
    Icon
  },
  directives: {
    outside
  },
  props: {
    value: [String, Number],
    type: {
      type: String,
      validator (value) {
        return value === 'card'
      }
    },
    closeCallBack: {
      type: Function,
      default: () => {
        return true
      }
    }
  },
  data () {
    return {
      activeName: '',
      navList: [],
      hiddenList: [],
      minPadding: '',
      showInner: true,
      showHidden: false,
      hiddenNum: null
    }
  },
  computed: {
    classes () {
      return [
        'sh-tabs',
        {
          [`sh-tabs-${this.sizes}`]: !!this.sizes
        }
      ]
    },
    moreWidth () {
      return this.sizes !== 'large'
        ? this.sizes === 'middle'
          ? '40px'
          : '32px'
        : '46px'
    }
  },
  watch: {
    value (val) {
      if (this.activeName !== val) {
        this.activeName = val
      }
      this.changeChildState(val)
    }
  },
  mounted () {
    if (!this.value) {
      this.navList[0].active = true
      for (let i = 0; i < this.$children.length; i++) {
        if (this.$children[i].$options.name === 'TabPane') {
          this.$children[i].active = true
          break
        }
      }
      this.activeName = this.navList[0].name
    }
  },
  methods: {
    clickHeader (params) {
      if (params.disabled) {
        return
      }
      this.$emit('input', params.name)
      this.$emit('on-click', params.name)
      if (this.activeName !== params.name) {
        this.changeChildState(params.name)
      }
      this.activeName = params.name
    },
    // 主动销毁组件
    destoryCom (compoents) {
      if (compoents._watcher) {
        compoents._watcher.teardown()
      }
      let i = compoents._watchers.length
      while (i--) {
        compoents._watchers[i].teardown()
      }
      if (compoents._data.__ob__) {
        compoents._data.__ob__.vmCount--
      }
      compoents.$off()
      compoents.$destroy()
      compoents.$el.parentNode.removeChild(compoents.$el)
    },
    closeTab (name) {
      // 给与回调，用于外部控制是否关闭
      if (this.closeCallBack(name)) {
        this.navList = []
        // let tempChild = {}
        this.$children.forEach(child => {
          if (child.$options.name === 'TabPane') {
            if (child.name === name) {
            // tempChild = child
            } else {
              this.navList.push({
                disabled: child.disabled,
                icon: child.icon,
                label: child.label,
                name: child.name,
                active: child.active,
                closed: child.closed
              })
            }
          }
        })
        if (this.navList.length > 0) { // 表明关闭之前还有两个tabs
          if (name === this.activeName) {
            let name = this.navList[this.navList.length - 1].name
            this.activeName = name
            this.$emit('input', name)
          }
        } else {
          this.$emit('input', null)
        }
        // 在tabPane可变的情况下，不需要销毁组件
        // this.destoryCom(tempChild)
        this.$emit('on-close', name)
      }
    },
    changeChildState (value = this.value || this.activeName, childrenList = this.$children) {
      this.navList = []
      childrenList.forEach(child => {
        if (child.$options.name === 'TabPane') {
          if (child.name === value) {
            child.active = true
          } else {
            child.active = false
          }
          this.navList.push({
            disabled: child.disabled,
            icon: child.icon,
            label: child.label,
            name: child.name,
            active: child.active,
            closed: child.closed
          })
        }
      })
      this.$nextTick(() => {
        const wrap = this.$refs.tabsHeader
        const inner = this.$refs.span[1]
        if (!wrap || !inner) { return }
        let temp = '16px 1%'
        if (this.sizes === 'middle') {
          temp = '13px 0.7%'
        } else if (this.sizes === 'small') {
          temp = '10px 0.7%'
        }
        if (inner.clientWidth <= 15 && this.minPadding === temp) {
          this.showInner = false
        } else if (inner.clientWidth > 14 && !this.showInner) {
          this.showInner = true
        }
        if (wrap.scrollWidth > wrap.clientWidth || wrap.offsetWidth > wrap.clientWidth) {
          if (!this.hiddenNum) {
            this.hiddenNum = this.navList.length
          }
          // 后续考虑resize事件，以及其余情况更新hiddenNum
          if (inner.clientWidth < 110 && this.minPadding === '') {
            this.minPadding = temp
          }
        } else if (this.navList.length < this.hiddenNum) {
          this.hiddenList = []
          this.showHidden = false
          if (this.minPadding === temp) {
            this.minPadding = ''
          }
        }
        if (this.minPadding === temp) {
          this.hiddenList = this.navList
        }
      })
    }
  }
}
</script>
